package com.nineclock.system.service.impl;

import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.nineclock.common.enums.ResponseEnum;
import com.nineclock.common.exception.NcException;
import com.nineclock.common.threadlocal.CurrentUserHolder;
import com.nineclock.common.utils.BeanHelper;
import com.nineclock.message.enums.MessageTypeEnum;
import com.nineclock.message.pojo.NcMessage;
import com.nineclock.system.dto.*;
import com.nineclock.system.mapper.*;
import com.nineclock.system.pojo.*;
import com.nineclock.system.service.SmsService;
import com.nineclock.system.service.SysCompanyService;
import com.nineclock.system.service.SysCompanyUserService;
import com.nineclock.system.utils.HxImManager;
import lombok.extern.slf4j.Slf4j;
import org.apache.rocketmq.spring.core.RocketMQTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.Collections;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

@Service
@Transactional
@Slf4j
public class SysCompanyServiceImpl implements SysCompanyService {

    @Autowired
    private SysCompanyUserMapper companyUserMapper;
    @Autowired
    private SysCompanyMapper companyMapper;

    @Override
    public List<SysCompanyDTO> queryCompanyByUserId(Long userId) {
        //校验参数
        if(userId == null){
            throw new NcException(ResponseEnum.INVALID_PARAM_ERROR);
        }

        /*
        //组装查询条件 ---> 根据用户ID查询企业ID  --->  where user_id = 30;
        LambdaQueryWrapper<SysCompanyUser> companyUserWrapper = new LambdaQueryWrapper<>();
        companyUserWrapper.eq(SysCompanyUser::getUserId, userId);

        List<SysCompanyUser> companyUserList = companyUserMapper.selectList(companyUserWrapper);

        //判定
        if(CollectionUtil.isEmpty(companyUserList)){
            throw new NcException(ResponseEnum.USER_NOT_JOIN_COMPANY);
        }

        //获取企业ID集合
        List<Long> idList = companyUserList.stream().map(sysCompanyUser -> {
            return sysCompanyUser.getCompanyId();
        }).collect(Collectors.toList());


        //组装条件 ------> 根据企业ID查询企业列表 ----> where id in (1,3);
        LambdaQueryWrapper<SysCompany> companyWrapper = new LambdaQueryWrapper<>();
        companyWrapper.in(SysCompany::getId, idList);

        List<SysCompany> companyList = companyMapper.selectList(companyWrapper);
        */

        List<SysCompany> companyList = companyMapper.queryCompanyByUserId(userId);

        //组装数据返回
        return BeanHelper.copyWithCollection(companyList, SysCompanyDTO.class);
    }



    @Override
    public SysCompanyDTO queryCompany() {

        //获取当前登录用户关联的企业ID
        Long companyId = CurrentUserHolder.get().getCompanyId();

        //根据企业ID查询企业信息
        SysCompany company = companyMapper.selectById(companyId);
        if(company == null){
            throw new NcException(ResponseEnum.COMPANY_NOT_FOUND);
        }

        //组装结果并返回
        return BeanHelper.copyProperties(company, SysCompanyDTO.class);
    }





    @Override
    public void updateCompany(SysCompanyDTO companyDTO) {
        //参数校验
        if(companyDTO == null || StrUtil.isEmpty(companyDTO.getName()) || StrUtil.isEmpty(companyDTO.getLogo())){
            throw new NcException(ResponseEnum.INVALID_PARAM_ERROR);
        }

        //组装企业数据信息，更新企业信息
        Long companyId = CurrentUserHolder.get().getCompanyId();
        SysCompany company = BeanHelper.copyProperties(companyDTO, SysCompany.class);
        company.setId(companyId);
        companyMapper.updateById(company);


        //更新企业员工 - SysCompanyUser 信息
        //update sys_company_user set company_name = '传智教育' where company_id = 1;

        companyUserMapper.updateCompanyUserByCompanyId(companyDTO.getName(), companyId);

    }


    @Autowired
    private SmsService smsService;
    @Autowired
    private SysCompanyUserService companyUserService;
    @Autowired
    private SysRoleMapper roleMapper;
    @Autowired
    private SysCompanyUserRoleMapper companyUserRoleMapper;

    @Override
    public void changeAdmin(SysChangeMainManagerDTO managerDTO) {
        // 校验参数
        if(managerDTO == null || StrUtil.isEmpty(managerDTO.getCode()) || managerDTO.getUserId() == null){
            throw new NcException(ResponseEnum.INVALID_PARAM_ERROR);
        }
        Long companyId = CurrentUserHolder.get().getCompanyId();



        // 获取当前用户基本信息
        SysCompanyUser companyUser = companyUserMapper.selectById(managerDTO.getUserId());
        String mobile = companyUser.getMobile();

        // 校验验证码
        Boolean verify = smsService.verify(managerDTO.getCode(), mobile, "3");
        if(!verify){
            throw new NcException(ResponseEnum.CODE_IMAGE_ERROR);
        }





        // 删除原来的系统管理员
        //①. 获取原来的系统管理员
        SysCompanyUserDTO companyUserDTO = companyUserService.queryCurrentAdmin(); //老的管理员

        //②. 查询当前企业系统管理员的角色ID
        LambdaQueryWrapper<SysRole> roleWrapper = new LambdaQueryWrapper<>();
        roleWrapper.eq(SysRole::getRoleName, "ROLE_ADMIN_SYS");
        roleWrapper.eq(SysRole::getCompanyId, companyId);

        SysRole sysRole = roleMapper.selectOne(roleWrapper);

        //③. 删除员工-角色关联关系
        LambdaQueryWrapper<SysCompanyUserRole> deleteWrapper = new LambdaQueryWrapper<>();
        deleteWrapper.eq(SysCompanyUserRole::getCompanyId, companyId);
        deleteWrapper.eq(SysCompanyUserRole::getRoleId, sysRole.getId());
        deleteWrapper.eq(SysCompanyUserRole::getCompanyUserId, companyUserDTO.getId());

        companyUserRoleMapper.delete(deleteWrapper);





        // 添加新的系统管理员
        SysCompanyUserRole companyUserRole = new SysCompanyUserRole();
        companyUserRole.setCompanyId(companyId);
        companyUserRole.setRoleId(sysRole.getId());
        companyUserRole.setCompanyUserId(managerDTO.getUserId());

        companyUserRoleMapper.insert(companyUserRole);






        //删除redis中验证码信息
        smsService.deleteCode(mobile, "3");
    }


    @Override
    public List<SysCompanyDTO> queryByKeyword(String keyword) {
        //检验
        if(StrUtil.isEmpty(keyword)){
            throw new NcException(ResponseEnum.INVALID_PARAM_ERROR);
        }

        //组装条件查询 ----> where name like '%传智%'
        LambdaQueryWrapper<SysCompany> wrapper = new LambdaQueryWrapper<>();
        wrapper.like(SysCompany::getName, keyword);

        List<SysCompany> companyList = companyMapper.selectList(wrapper);

        //返回结果
        return BeanHelper.copyWithCollection(companyList, SysCompanyDTO.class);
    }

    @Autowired
    private SysUserMapper userMapper;
    @Autowired
    private RocketMQTemplate rocketMQTemplate;
    @Autowired
    private HxImManager hxImManager;

    @Override
    public void applyJoinCompany(SysApplyJoinCompanyUserDTO companyUserDTO) {
        //校验参数
        if(companyUserDTO == null || StrUtil.isEmpty(companyUserDTO.getUserName()) || companyUserDTO.getCompanyId()==null){
            throw new NcException(ResponseEnum.INVALID_PARAM_ERROR);
        }

        //组装企业员工数据, 插入到企业员工表
        SysCompanyUser companyUser = new SysCompanyUser();
        companyUser.setCompanyId(companyUserDTO.getCompanyId());
        companyUser.setUserName(companyUserDTO.getUserName());
        companyUser.setUserId(companyUserDTO.getUserId());
        companyUser.setEmail(companyUserDTO.getEmail());
        companyUser.setMobile(companyUserDTO.getMobile());
        companyUser.setRemark(companyUserDTO.getApplyReason());
        companyUser.setPost(companyUserDTO.getPost());
        companyUser.setImageUrl(companyUserDTO.getImageUrl());
        companyUser.setCompanyName(companyUserDTO.getCompanyName());

        companyUser.setEnable((short)0);
        companyUserMapper.insert(companyUser);


        //完善用户的基本信息 ----> 更新
        SysUser sysUser = userMapper.selectById(companyUserDTO.getUserId());
        if(sysUser != null){
            sysUser.setUsername(companyUserDTO.getUserName());
            sysUser.setLastLoginCompanyId(companyUserDTO.getCompanyId());//设置用户的最后登录的企业ID为当前加入企业的ID
            sysUser.setEmail(companyUserDTO.getEmail());
            userMapper.updateById(sysUser);
        }


        //------------------------------ 推送消息
        //获取当前系统管理员
        SysCompanyUser admin = companyUserMapper.queryCurrentAdminByCompanyId(companyUserDTO.getCompanyId());//companyUserService.queryCurrentAdmin();

        //发送消息到MQ
        NcMessage ncMessage = new NcMessage();
        ncMessage.setCompanyId(String.valueOf(companyUserDTO.getCompanyId()));
        ncMessage.setApplyUserId(companyUserDTO.getUserId());//申请用户ID
        ncMessage.setApplyUsername(companyUserDTO.getUserName());//申请用户名
        ncMessage.setApproveStatue(0);//审核状态
        ncMessage.setUseStatus(0);//未读
        ncMessage.setContent(companyUserDTO.getUserName()+" 申请加入企业,请及时审批!");


        ncMessage.setApproveUserId(admin.getUserId());//审核用户ID
        ncMessage.setApproveUsername(admin.getUserName());//审核用户名

        ncMessage.setCreateTime(new Date());
        ncMessage.setTargets(Collections.singletonList(admin.getMobile()));//推送目标 , 按照别名推送 ----> 手机号
        ncMessage.setMessageType(MessageTypeEnum.COMPANY_APPLY.getType());//消息类型

        //发送消息到MQ
        rocketMQTemplate.convertAndSend("messagePushTopic", ncMessage);
        log.info("发送消息到MQ , :" + ncMessage);


        //--------------------------> 注册用户到环信
        sysUser.setPassword("123456");
        sysUser.setUsername(sysUser.getMobile());
        hxImManager.registerUser2HuanXing(sysUser);
        log.info("用户申请加入企业后, 注册用户到环信 ...............");
    }


    @Override
    public void allowedJoinCompany(SysAllowedJoinCompanyUserDTO allowedDto) {
        //校验
        if(allowedDto == null){
            throw new NcException(ResponseEnum.INVALID_PARAM_ERROR);
        }

        //更新员工状态
        LambdaQueryWrapper<SysCompanyUser> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(SysCompanyUser::getUserId, allowedDto.getApplyUserId());
        wrapper.eq(SysCompanyUser::getCompanyId, CurrentUserHolder.get().getCompanyId());

        SysCompanyUser companyUser = companyUserMapper.selectOne(wrapper);
        if(companyUser != null){//存在 , 更新
            companyUser.setEnable(allowedDto.getApproved()?(short)1:(short)0);
            companyUserMapper.updateById(companyUser);
        }

        if(allowedDto.getApproved()){
            //发送消息到MQ --------> 修改消息的状态
            rocketMQTemplate.convertAndSend("allowedJoinCompanyTopic", allowedDto.getNotifyMsgId());



            //发送消息到MQ --------> 推送消息给申请用户
            SysUser sysUser = userMapper.selectById(allowedDto.getApplyUserId());

            NcMessage ncMessage = new NcMessage();
            ncMessage.setCompanyId(CurrentUserHolder.get().getCompanyId()+"");
            ncMessage.setApplyUserId(allowedDto.getApplyUserId());//申请用户ID
            ncMessage.setApplyUsername(sysUser.getUsername());
            ncMessage.setContent("您的申请加入企业的请求, 已经审核通过");

            ncMessage.setApproveUserId(CurrentUserHolder.get().getId());//审核用户ID
            ncMessage.setCreateTime(new Date());

            ncMessage.setTargets(Collections.singletonList(sysUser.getMobile()));//推送目标 , 按照别名推送 ----> 手机号
            ncMessage.setMessageType(MessageTypeEnum.COMPANY_APPLY_PASS.getType());//消息类型 ---> 审核通过

            //发送消息到MQ
            rocketMQTemplate.convertAndSend("messagePushTopic", ncMessage);
            log.info("发送消息到MQ , :" + ncMessage);

        }
    }
}
